#include "tim.h"

#include "led.h"

static void tim_nvic_init()
{
    NVIC_InitType NVIC_InitStruct;

    /* Enable the TIM3 global Interrupt */
    NVIC_InitStruct.NVIC_IRQChannel                   = TIM3_IRQn;
    NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority = 0;
    NVIC_InitStruct.NVIC_IRQChannelSubPriority        = 10;
    NVIC_InitStruct.NVIC_IRQChannelCmd                = ENABLE;

    NVIC_Init(&NVIC_InitStruct);
}

void tim_init(uint16_t prescaler, uint16_t period)
{
	/* Initialzie the TimeBase */
	TIM_TimeBaseInitType TIM_TimeBaseInitSrtuct;
	
	/* APB1 36 MHz max tim3 clock 72 MHz */
	RCC_ConfigPclk1(RCC_HCLK_DIV4);
	/* TIM3 clock enable */
    RCC_EnableAPB1PeriphClk(RCC_APB1_PERIPH_TIM3, ENABLE);
	
	TIM_TimeBaseInitSrtuct.Period = period;
	TIM_TimeBaseInitSrtuct.Prescaler = prescaler;
	TIM_TimeBaseInitSrtuct.ClkDiv = 0;
	TIM_TimeBaseInitSrtuct.CntMode = TIM_CNT_MODE_UP;
	TIM_InitTimeBase(TIM3, &TIM_TimeBaseInitSrtuct);
	TIM_ConfigInt(TIM3, TIM_INT_UPDATE, ENABLE);
	tim_nvic_init();
	
	/* Initialzie the PWM */
	GPIO_InitType GPIO_InitStruct;
	
    RCC_EnableAPB2PeriphClk(RCC_APB2_PERIPH_AFIO | RCC_APB2_PERIPH_GPIOB, ENABLE);
	
	/* TIM3 Channel2 PWM GPIO Configration(PinRemap) */
    GPIO_InitStruct.Pin        = GPIO_PIN_5;
    GPIO_InitStruct.GPIO_Mode  = GPIO_Mode_AF_PP;
    GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_InitPeripheral(GPIOB, &GPIO_InitStruct);
	GPIO_ConfigPinRemap(GPIO_PART1_RMP_TIM3, ENABLE);
	
	/* TIM3 Channel2 PWM Configration */
	OCInitType TIM_OCInitStruct;
	TIM_OCInitStruct.OcMode      = TIM_OCMODE_PWM1;
    TIM_OCInitStruct.OutputState = TIM_OUTPUT_STATE_ENABLE;
    TIM_OCInitStruct.Pulse       = 1000;
    TIM_OCInitStruct.OcPolarity  = TIM_OC_POLARITY_HIGH;
	TIM_InitOc2(TIM3, &TIM_OCInitStruct);
	TIM_ConfigOc2Preload(TIM3, TIM_OC_PRE_LOAD_ENABLE);
	
	TIM_Enable(TIM3, ENABLE);
}

void TIM3_IRQHandler()
{
	if (TIM_GetIntStatus(TIM3, TIM_INT_UPDATE) != RESET)
	{
		led3_blink();
		TIM_ClrIntPendingBit(TIM3, TIM_INT_UPDATE);
	}
}

